﻿using Autofac;
using CrawlerApp.Core.Entities;
using CrawlerApp.Core.Entities.BookAggregate;
using CrawlerApp.Infrastructure.Data;
using Microsoft.EntityFrameworkCore;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Linq.Expressions;
using System.Threading;
using System.Threading.Tasks;

namespace CrawlerApp.Infrastructure.Services
{
    public class BookRepository : Repository<Book>, IBookRepository
    {
        public BookRepository(/*ApplicationDbContext context*/ILifetimeScope lifetimeScope) : base(lifetimeScope) { }

        public async Task<IReadOnlyCollection<Book>> GetBookByAuthorAsync(string author, CancellationToken cancellationToken = default)
        {
            using (var context = lifetimeScope.Resolve<ApplicationDbContext>())
            {
                return await context.Set<Book>()
                .AsNoTracking()
                //.Include(it => it.BookInfo.Author)
                .Where(it => it.Author.Name == author)
                .ToListAsync(cancellationToken);
            }
        }

        public async Task<IReadOnlyCollection<Book>> GetBookListByCategoryAsync(string categoryName, CancellationToken cancellationToken = default)
        {
            using (var context = lifetimeScope.Resolve<ApplicationDbContext>())
            {
                return await context.Set<Book>()
                .AsNoTracking()
                //.Include(it => it.BookInfo.Category)
                .Where(it => it.Category.Name == categoryName)
                .ToListAsync(cancellationToken);
            }
        }

        public async Task<IReadOnlyCollection<BookRank>> GetBookRanksAsync(Expression<Func<BookRank, int>> order, CancellationToken cancellationToken = default)
        {
            using (var context = lifetimeScope.Resolve<ApplicationDbContext>())
            {
                return await context.Set<Book>()
                .AsNoTracking()
                .Select(it => new BookRank(it.Name, it.Vote))
                .OrderByDescending(order)
                .ToListAsync(cancellationToken);
            }
        }
    }
}
